package cluster_node.listener;

import cluster_node.scheduler.service.UploadScheduleService;
import cluster_node.serialization.ModelSerializer;
import com.eclipsesource.json.JsonObject;
import org.eclipse.leshan.core.node.LwM2mSingleResource;
import org.eclipse.leshan.core.observation.Observation;
import org.eclipse.leshan.core.request.ReadRequest;
import org.eclipse.leshan.server.californium.LeshanServer;
import org.eclipse.leshan.server.registration.Registration;
import org.eclipse.leshan.server.registration.RegistrationListener;
import org.eclipse.leshan.server.registration.RegistrationUpdate;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.util.Pool;

import java.util.Collection;
import java.util.Map;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;

public class UploadRegistrationListener implements RegistrationListener {

    private final static Logger LOG = LoggerFactory.getLogger(UploadRegistrationListener.class);

    private final static String REGISTER_CHANNEL = "LESHAN_REG_MODEL";

    private Pool<Jedis> pool;
    private LeshanServer server;
    private UploadScheduleService scheduleService;

    public UploadRegistrationListener(Pool<Jedis> pool, LeshanServer server, UploadScheduleService scheduleService) {
        this.pool = pool;
        this.server = server;
        this.scheduleService = scheduleService;
    }

    public void registered(Registration registration, Registration registration1, Collection<Observation> collection) {
        JsonObject jsonModel = ModelSerializer.serializeToJson(server.getModelProvider().getObjectModel(registration));
        jsonModel.add("ep", registration.getEndpoint());

        Map<String, String> additionalRegistrationAttributes = registration.getAdditionalRegistrationAttributes();
        String type = additionalRegistrationAttributes.getOrDefault("model", "DEFAULT");

        LOG.info("register from [{}, {}]", type, registration.getEndpoint());

        scheduleService.register(type, registration);

        try (Jedis jedis = pool.getResource()) {
            jedis.publish(REGISTER_CHANNEL, jsonModel.toString());
        }
    }

    public void updated(RegistrationUpdate registrationUpdate, Registration registration, Registration previousReg) {

    }

    public void unregistered(Registration registration, Collection<Observation> collection, boolean expired, Registration previousReg) {
        LOG.info("deregister from [{}]", registration.getEndpoint());
        scheduleService.deregister(registration);
    }
}
